import { Injectable, Inject, BadRequestException } from '@nestjs/common';
import { InjectModel } from '@nestjs/mongoose';
import { Model, Connection } from 'mongoose';
import { Motion } from 'src/schemas/motion.schema';
import { RecordService } from '../record/record.service';

import CreateMotionDto from './dto/create.motion.dto';
import UpdateMotionDto from './dto/update.motion.dto';

@Injectable()
export class MotionService {
  constructor(
    @InjectModel(Motion.name) private motionModel: Model<Motion>,
    private readonly recordService: RecordService,
    @Inject('DATABASE_CONNECTION')
    private readonly connection: Connection,
  ) {}
  async getMotions(userId: string) {
    return await this.motionModel.find({
      $or: [{ userId: userId }, { userId: null }],
    });
  }

  async getMotion(motionId: string) {
    return await this.motionModel.findById(motionId).select('-userId');
  }

  async createMotion(userId: string, dto: CreateMotionDto) {
    return await this.motionModel.create({
      ...dto,
      userId,
    });
  }

  async deleteMotion(motionId: string) {
    const exist = await this.recordService.existsByMotionId(motionId);
    if (exist) {
      throw new BadRequestException('记录中存在该运动, 无法删除');
    }
    return await this.motionModel.findByIdAndDelete(motionId);
  }

  async deleteMotionAndRecords(userId: string, motionId: string) {
    const session = await this.connection.startSession();
    try {
      await session.startTransaction();

      // 1. 删除记录
      await this.recordService.deleteRecordsByMotion(userId, motionId, session);

      // 2. 删除运动数据
      const result = await this.motionModel
        .findByIdAndDelete(motionId)
        .session(session);

      await session.commitTransaction();
      return result;
    } catch (error) {
      await session.abortTransaction();
      throw error;
    } finally {
      session.endSession();
    }
  }

  async updateMotion(motionId: string, dto: UpdateMotionDto) {
    return await this.motionModel.findByIdAndUpdate(motionId, dto);
  }
}
